package com.ct.R.Result;

import com.ct.R.IResultCodeInterface;
import com.ct.R.Result.ResultEnum.ResultCodeEnum;
import lombok.Data;

@Data
public class Result<T> {
    /**
     * 业务错误码
     */
    private Integer code;
    /**
     * 业务错误码描述
     */
    private String codeDesc;
    /**
     * 描述
     */
    private String msg;
    /**
     * 结果集
     */
    private T data;


    //region  构造函数和链式调用
    private Result() {
    }

    // 私有化的目的：不是单列，是为了约束外界不允许通过实例化和set方法的方式进行复制调用返回
    // 全部统一使用静态方法 success和fail进行调用。从而达到统一的目的


    public Result(Integer code, String codeDesc, String msg, T data) {
        this.code = code;
        this.codeDesc = codeDesc;
        this.msg = msg;
        this.data = data;
    }

    /**
     * 返回当前对象，支持链式调用
     */
    public Result code(Integer code) {
        this.setCode(code);
        return this;
    }


    /**
     * 返回当前对象，支持链式调用
     */
    public Result msg(String msg) {
        this.setMsg(msg);
        return this;
    }

    /**
     * 返回当前对象，支持链式调用
     */
    public Result codeDesc(String codeDesc) {
        this.setCodeDesc(codeDesc);
        return this;
    }
    //endregion
    //  --------------------------------------------------------------------------------------------------------------------------------------------


    /**
     * 成功的返回
     *
     * @param data
     * @return
     */
    public static <T> Result success(T data) {
        return new Result(
                ResultCodeEnum.SUCCESS.getCode(),
                ResultCodeEnum.SUCCESS.getCodeDesc(),
                ResultCodeEnum.SUCCESS.getMsg(),
                data);
    }


    /**
     * 成功方法的封装
     * 成功只有一种 200 成功
     * 失败就N中，也就code不同，原因不同，
     *
     * @param code
     * @param msg
     * @return
     */
    public static Result fail(Integer code, String msg) {
        return new Result(
                code,
                ResultCodeEnum.FAIL.getCodeDesc(),
                msg,
                null);
    }

    public static Result fail(Integer code, String codeDesc, String msg) {
        return new Result(
                code,
                codeDesc,
                msg,
                null
        );
    }

    public static Result fail(IResultCodeInterface iResultCodeInterface) {
        return new Result(
                iResultCodeInterface.getCode(),
                iResultCodeInterface.getCodeDesc(),
                iResultCodeInterface.getMsg(),
                null);
    }

}